package com.alibaba.citrus.cr.mn.order.center.facade.service.impl;

import com.alibaba.citrus.cr.common.annotation.FacadeInvoker;
import com.alibaba.citrus.cr.common.enums.ordercenter.ExchangeOrderTypeEnum;
import com.alibaba.citrus.cr.common.enums.ordercenter.OrderCategoryEnum;
import com.alibaba.citrus.cr.common.enums.ordercenter.ReturnOrderTypeEnum;
import com.alibaba.citrus.cr.common.enums.ordercenter.SalesOrderTypeEnum;
import com.alibaba.citrus.cr.mn.order.center.common.util.StopWatchUtils;
import com.alibaba.citrus.cr.mn.order.center.facade.adapter.BaseDataServiceAdapter;
import com.alibaba.citrus.cr.mn.order.center.facade.function.convert.ObtcSaleOrderLineIndexToResponseConvertor;
import com.alibaba.citrus.cr.mn.order.center.facade.service.OrderBizDomainService;
import com.alibaba.cloud.retail.delivery.api.model.delivery.enums.OrderTagEnum;
import com.alibaba.cz.base.tool.Nullable;
import com.alibaba.cz.base.tool.log.Log;
import com.alibaba.fastjson.JSON;
import com.alibaba.lattice2.epoch.sdk.model.Result;
import com.epoch.app.crb2btradecenter.cbtcobtcorderadb.model.CbtcObtcOrderAdb;
import com.epoch.app.crb2btradecenter.cbtcobtcorderadb.service.CbtcObtcOrderAdbService;
import com.epoch.app.crb2btradecenter.cbtcobtcorderlineadb.model.CbtcObtcOrderLineAdb;
import com.epoch.app.crb2btradecenter.cbtcobtcorderlineadb.service.CbtcObtcOrderLineAdbService;
import com.epoch.app.crb2btradecenter.model.dto.CbtcObtcOrderAdbRequest;
import com.epoch.app.crb2btradecenter.model.dto.CbtcObtcOrderLineAdbRequest;
import com.epoch.app.crb2btradecenter.obtcsaleorderlineindex.model.ObtcSaleOrderLineIndex;
import com.epoch.app.mnordercenter.model.dto.*;
import com.epoch.app.mnordercenter.orderlinequery.service.OrderLineQueryService;
import com.google.common.collect.Iterables;
import com.google.common.collect.Lists;
import org.apache.commons.collections4.CollectionUtils;
import org.apache.commons.lang3.StringUtils;
import org.springframework.context.annotation.Primary;
import org.springframework.stereotype.Component;
import org.springframework.util.StopWatch;

import javax.annotation.Resource;
import java.util.*;
import java.util.stream.Collectors;

import static com.alibaba.citrus.cr.mn.order.center.common.SetOrderTag.*;

/**
 * @author zhoubc
 * @date 2023/5/23 15:55
 */
@Primary
@Component
public class OrderLineQueryServiceImpl implements OrderLineQueryService {
    Log log = Log.getLogger(OrderLineQueryServiceImpl.class);

    @Resource
    private OrderBizDomainService orderBizDomainService;
    @Resource
    private BaseDataServiceAdapter baseDataServiceAdapter;
    @Resource
    private CbtcObtcOrderAdbService cbtcObtcOrderAdbService;
    @Resource
    private CbtcObtcOrderLineAdbService cbtcObtcOrderLineAdbService;

    @Override
    @FacadeInvoker
    public Result<List<OrderLineBizQueryResponse>> pageQueryFromES(OrderLineBizQueryRequest orderLineBizQueryRequest) {
        //页面查询订单类型
        if (CollectionUtils.isEmpty(orderLineBizQueryRequest.getOrderTypeList())
                && StringUtils.isNotBlank(orderLineBizQueryRequest.getQueryOrderType())) {
            List<DictionaryResponse> list = baseDataServiceAdapter.queryDictionarys(orderLineBizQueryRequest.getQueryOrderType());
            orderLineBizQueryRequest.setOrderTypeList(Nullable.stream(list).map(x->x.getCode()).collect(Collectors.toList()));
        }
        return orderBizDomainService.pageQueryOrderLineList(orderLineBizQueryRequest);
    }

    @Override
    public Result<List<PageQuerySaleOrderDetailResponse>> loadDetailBizForPage(SalesOrderAtomPageQueryRequest request) {
        request.setOrderCategoryCodeList(OrderCategoryEnum.codes());
        request.setOrderTagList(Lists.newArrayList(EXCHANGE, RETURN, NORMAL));
        if (CollectionUtils.isEmpty(request.getSalesOrderTypeList())) {
            List<String> salesOrderTypeList = Lists.newArrayList(Iterables.concat(SalesOrderTypeEnum.companyOrderCodes(), ReturnOrderTypeEnum.codes(), ExchangeOrderTypeEnum.codes()));
            request.setSalesOrderTypeList(salesOrderTypeList);
        }
        Result<List<ObtcSaleOrderLineIndex>> loadDetailForPage = orderBizDomainService.loadDetailForPage(request);
        List<PageQuerySaleOrderDetailResponse> response = ObtcSaleOrderLineIndexToResponseConvertor.convert(loadDetailForPage, null);
        Result<List<PageQuerySaleOrderDetailResponse>> result = Result.success(response, "", "");
        result.setTotal(loadDetailForPage.getTotal());
        return result;
    }

    @Override
    public Result<List<PageQuerySaleOrderDetailResponse>> loadDetailGroupForPage(SalesOrderGroupPageQueryRequest request) {
        // F-B销售&退货订单明细列表查询内部接口（同时查出销售单和退货单）
        SalesOrderAtomPageQueryRequest salesOrderAtomPageQueryRequest = JSON.parseObject(JSON.toJSONString(request), SalesOrderAtomPageQueryRequest.class);
        salesOrderAtomPageQueryRequest.setOrderCategoryCodeList(Lists.newArrayList(OrderCategoryEnum.GROUP.getCode(), OrderCategoryEnum.STOCK.getCode()));
        salesOrderAtomPageQueryRequest.setOrderTagList(Lists.newArrayList(NORMAL, RETURN));
        if (CollectionUtils.isEmpty(salesOrderAtomPageQueryRequest.getSalesOrderTypeList())) {
            List<String> salesOrderTypeList = Lists.newArrayList(Iterables.concat(SalesOrderTypeEnum.groupOrderCodes(), ReturnOrderTypeEnum.groupOrderCodes()));
            salesOrderAtomPageQueryRequest.setSalesOrderTypeList(salesOrderTypeList);
        }
        Result<List<ObtcSaleOrderLineIndex>> loadDetailForPage = orderBizDomainService.loadDetailForPage(salesOrderAtomPageQueryRequest);
        List<PageQuerySaleOrderDetailResponse> response = ObtcSaleOrderLineIndexToResponseConvertor.convert(loadDetailForPage, OrderCategoryEnum.GROUP.getCode());
        Result<List<PageQuerySaleOrderDetailResponse>> result = Result.success(response, "", "");
        result.setTotal(loadDetailForPage.getTotal());
        return result;
    }

    @Override
    public Result<List<UnconfirmedQuantityResponse>> queryUnconfirmedQuantity(UnconfirmedQuantityRequest unconfirmedQuantityRequest) {
        StopWatchUtils.start("查询未确认数量", "queryUnconfirmedQuantity");
        log.info("OrderLineQueryServiceImpl#queryUnconfirmedQuantity unconfirmedQuantityRequest:{}", JSON.toJSONString(unconfirmedQuantityRequest));
        List<UnconfirmedQuantityResponse> responses = new ArrayList<>();
        List<String> businessUnitCodeListWithF2B = new ArrayList<>();
        List<String> businessUnitCodeListWithB2b = new ArrayList<>();
        unconfirmedQuantityRequest.getBusinessUnitCodeList().forEach(businessUnitCode -> {
            if ("600020".equals(businessUnitCode) || "1171".equals(businessUnitCode)) {
                businessUnitCodeListWithF2B.add(businessUnitCode);
            } else {
                businessUnitCodeListWithB2b.add(businessUnitCode);
            }
        });
        log.info("OrderLineQueryServiceImpl#queryUnconfirmedQuantity unconfirmedQuantityWithF2B:{}; unconfirmedQuantityWithB2b:{}", JSON.toJSONString(businessUnitCodeListWithF2B), JSON.toJSONString(businessUnitCodeListWithB2b));
        StopWatchUtils.start("查询未确认数量", "F_B_query");
        List<UnconfirmedQuantityResponse> unconfirmedQuantityWithF2B = queryOrderByAdb(unconfirmedQuantityRequest, businessUnitCodeListWithF2B, OrderCategoryEnum.GROUP.getCode());
        StopWatchUtils.stop();
        StopWatchUtils.start("查询未确认数量", "B_b_query");
        // List<UnconfirmedQuantityResponse> unconfirmedQuantityWithB2b = queryOrderByAdb(unconfirmedQuantityRequestList, businessUnitCodeListWithB2b, OrderCategoryEnum.COMPANY.getCode());
        StopWatchUtils.stop();
        // log.info("OrderLineQueryServiceImpl#queryUnconfirmedQuantity unconfirmedQuantityWithF2B:{}; unconfirmedQuantityWithB2b:{}", JSON.toJSONString(unconfirmedQuantityWithF2B), JSON.toJSONString(unconfirmedQuantityWithB2b));
        responses.addAll(unconfirmedQuantityWithF2B);
        // responses.addAll(unconfirmedQuantityWithB2b);
        StopWatchUtils.stop();
        StopWatchUtils.print("OrderLineQueryServiceImpl#queryUnconfirmedQuantity");
        return Result.success(responses);
    }

    private List<UnconfirmedQuantityResponse> queryOrderByAdb(UnconfirmedQuantityRequest unconfirmedQuantityRequest, List<String> businessUnitCodeList, String orderCategoryCode) {
        if (CollectionUtils.isEmpty(businessUnitCodeList)) {
            return Lists.newArrayList();
        }
        CbtcObtcOrderLineAdbRequest cbtcObtcOrderLineAdbRequest = CbtcObtcOrderLineAdbRequest.builder()
                .bisUnitOutCodeList(businessUnitCodeList)
                .warehouseCodeList(unconfirmedQuantityRequest.getWarehouseCodeList())
                .productCodeList(unconfirmedQuantityRequest.getProductCodeList())
                .orderCategoryCode(orderCategoryCode)
                .orderTag(OrderTagEnum.NORMAL.getCode())
                .build();
        StopWatch sw = new StopWatch();
        sw.start();
        Result<List<com.epoch.app.crb2btradecenter.model.dto.UnconfirmedQuantityResponse>> adbOrderLineResult = cbtcObtcOrderLineAdbService.getUnconfirmedQuantity(cbtcObtcOrderLineAdbRequest);
        sw.stop();
        log.info("OrderLineQueryServiceImpl#queryUnconfirmedQuantity queryOrderByAdb time:{}", sw.getTotalTimeMillis());
        List<com.epoch.app.crb2btradecenter.model.dto.UnconfirmedQuantityResponse> result = adbOrderLineResult.getResult();
        if (!adbOrderLineResult.isSuccess() || CollectionUtils.isEmpty(result)) {
            return Lists.newArrayList();
        }
        return JSON.parseArray(JSON.toJSONString(result), UnconfirmedQuantityResponse.class);
    }
}
